const tencentcloud = require("tencentcloud-sdk-nodejs")
const aliyunApi = require('@alicloud/pop-core')
const utils = require('./utils.cjs')
const combinator = require('./combinator.cjs')
const {getWebDriver, driverGoto, elemFindItem, elemGetValue, elemGetText, elemClick, elemInput, elemInputSet, elemWaitUtil} = require('./webdriver.cjs')
const config = require('../config.cjs')
const R = require('ramda')
const md5 = require("md5")


const TmtClient = tencentcloud.tmt.v20180321.Client

function createTencentClient() {
    return new TmtClient({
        credential: {
            secretId: config.TencentSecretId,
            secretKey: config.TencentSecretKey,
        },
        region: "ap-guangzhou",
        profile: {
            httpProfile: {
                endpoint: "tmt.tencentcloudapi.com",
            },
        },
    })
}

function createAliyunClient() {
    return new aliyunApi({
        accessKeyId: process.env.AliSecretId,
        accessKeySecret: process.env.AliSecretKey,
        endpoint: 'https://mt.aliyuncs.com',
        apiVersion: '2018-10-12'
    });
}

async function transByBaiduApi(text, source, target) {
    function convert(url, args)
    {
	const str = R.map(function(item) {
	    return encodeURIComponent(item[0]) + '=' + encodeURIComponent(item[1])
	}, R.toPairs(args)).join('&')

	return url + '?' + str
    }
    const url = 'http://api.fanyi.baidu.com/api/trans/vip/translate'
    var appid = config.BaiduAppid
    var salt = utils.uuid()
    var key = config.BaiduKey
    var str1 = appid + text + salt +key;
    var sign = md5(str1);
    const url2 = convert(url, {
	q: text,
	appid,
        salt,
        from: source,
        to: target,
        sign
    })
    const rs = await utils.httpGet(url2)
    if (rs.data.trans_result) {
	return rs.data.trans_result[0]['dst']
    }
    else {
	console.log(rs.data)
	return ''
    }
}

let tencentClient = null
let aliClient = null


// 通过腾讯API进行翻译
async function transByTencentApi(text, source, target) {
    if (tencentClient == null) {
        tencentClient = createTencentClient()
    }

    const params = {
        "SourceText": text,
        "Source": source,
        "Target": target,
        "ProjectId": 0
    }
    const rs = await tencentClient.TextTranslate(params)
    return rs.TargetText
}

async function transByAliApi(text, source, target) {
    if (aliClient == null) {
        aliClient = createAliyunClient()
    }
    var params = {
        "SourceLanguage": source,
        "TargetLanguage": target,
        "SourceText": text,
        "FormatType": "text"
    }

    var requestOption = {
        method: 'POST'
    }
    const result = await aliClient.request('TranslateGeneral', params, requestOption)

    if (result.Code == 200) {
        return result.Data.Translated
    }
    else {
        throw new Error('阿里翻译有问题:' + result.Message)
    }
}

function cutTrans(trans, maxLen) {
    return combinator.wrapFnAsync(
	combinator.errorRetry(async function(text) {
            const rs = await trans(text)
	    await utils.sleep(200)  // 有些API每秒最多只能发送5次请求，只能卡速
	    return rs
	}, 3),
	async function(fn, text) {
            async function loop(text) {
		if (text === '') {
                    return text
		}
		let stringArr = []
		if (R.length(text) > maxLen) {
                    stringArr = utils.strSentenceCut(text, maxLen)
		}
		else {
                    stringArr = [text, '']
		}
		const s = stringArr[0]
		const rs = await fn(s)
		const leftRs = await loop(stringArr[1])
		return rs + leftRs
            }
            console.info("正在翻译")
            return await loop(text)
	}
    )
}



// 给driver初始化翻译界面
async function initTrans(driver, from, to) {
    await driver.url(`https://translate.google.cn/?sl=${from}&tl=${to}&op=translate`)
}

// 判断是否处于翻译界面
async function isTransPage(driver) {
    const url = await driver.getUrl()
    return url.includes("translate.google.cn")
}

// 比较慢，但可能效果最好
async function transByDriver1(text, from, to) {
    const driver = await getWebDriver('global')

    if (!(await isTransPage(driver))) {
        await initTrans(driver, from, to)
    }
    const inputField = await elemFindItem(driver, 'textarea[jsname="BJE2fc"]')

    const oldText = await elemGetValue(inputField)
    if (oldText != '') {
        const clearBtn = await elemFindItem(driver, 'button[aria-label="清除原文"]')
        await elemClick(clearBtn)
    }

    await elemInputSet(inputField, text)

    const outputField = await elemFindItem(driver, 'span[jsname="W297wb"]')
    let transText = await elemGetText(outputField)
    return transText
}


// 通过url直接访问，速度较快
async function transByDriver2(text, from, to) {
    const driver = await getWebDriver('global')
    const textEncode = utils.urlEncode(text)
    
    const url = `https://translate.google.cn/?sl=${from}&tl=${to}&op=translate&text=${textEncode}`

    await driverGoto(driver, url)

    const outputField = await elemFindItem(driver, 'span[jsname="W297wb"]')
    let transText = await elemGetText(outputField)
    return transText
}

// 这里需要占用剪切板，不是很好用
async function transByDriver3(text, from, to) {
    console.log("正在翻译: " + text)
    const globalWebDriver = await getWebDriver('global')
    if (!(await isTransPage(globalWebDriver))) {
        await initTrans(globalWebDriver, from, to)
    }

    const inputField = await elemFindItem(globalWebDriver, 'textarea[jsname="BJE2fc"]')

    const oldText = await elemGetValue(inputField)
    if (oldText != '') {
        const clearBtn = await elemFindItem(globalWebDriver, 'button[aria-label="清除原文"]')
        await elemClick(clearBtn)
    }

    clipboardy.writeSync(text)
    await inputField.click()
    await globalWebDriver.keys(['Control', 'v'])
    
    const outputField = await elemFindItem(globalWebDriver, 'span[jsname="W297wb"]')
    let transText = await elemGetText(outputField)
    return transText
}

async function transByBaiduDriver2(text, from, to) {
    const driver = await getWebDriver('global')
    const textEncode = utils.urlEncode(text)
    
    const url = `https://fanyi.baidu.com/?aldtype=16047#${from}/${to}/${textEncode}`

    await driverGoto(driver, url)

    const outputField = await elemFindItem(driver, 'p.ordinary-output.target-output.clearfix')
    let transText = await elemGetText(outputField)
    return transText
}



module.exports = {transByTencentApi, transByAliApi, transByBaiduDriver2, cutTrans, transByBaiduApi}

//console.log(await transByTencentApi('Thượng tá Nguyễn Văn Hiển, Phó Chính uỷ Bộ Tư lệnh Vùng Cảnh sát biển 1 cho biết: Cuộc thi là một trong những hoạt động công tác dân vận nổi bật của tuổi trẻ Bộ Tư lệnh Vùng với cách làm sáng tạo, hiệu quả nhằm tuyên truyền, giáo dục, nâng cao hiểu biết về biển, đảo Việt Nam, các quy định của pháp luật của Việt Nam và quốc tế liên quan đến biển, đảo cho các thầy cô giáo, học sinh và nhân dân địa phương.', 'vi', 'zh'))
